﻿using System.Collections.Generic;
using Infrastructure.IoC;
using Infrastructure.NinjectModules;
using Microsoft.Web.Infrastructure.DynamicModuleHelper;
using Ninject;
using Ninject.Modules;
using Ninject.Web.Mvc;
using SocialFront.Core.NinjectModules;

namespace SocialFront.Core.Initializers
{
    public static class NinjectBootStrapper
    {
        private static readonly IKernel Kernel = ObjectFactory.Kernel;

        private static readonly Bootstrapper Bootstrapper = new Bootstrapper();

        public static void Start()
        {
            DynamicModuleUtility.RegisterModule(typeof(OnePerRequestModule));
            DynamicModuleUtility.RegisterModule(typeof(HttpApplicationInitializationModule));
            try
            {
                Bootstrapper.Initialize(getKernel);
            }
            catch (System.Exception ex)
            {
                throw ex;
            }
        }

        public static void StartForUnitTest()
        {
            getKernel();
        }

        public static void Stop()
        {
            Bootstrapper.ShutDown();
        }

        private static IKernel getKernel()
        {
            var kernel = initializeKernel();

            return kernel;
        }

        private static IKernel initializeKernel()
        {
            registerKernelServices();
            storeKernelForApplicationUsage();

            return Kernel;
        }

        private static void registerKernelServices()
        {
            Kernel.Load(getNinjectModules());
        }

        private static void storeKernelForApplicationUsage()
        {
            // We set the kernel in the facade so it can be 
            // accessible throughout the application.
            Facade.Kernel = Kernel;
        }

        private static IEnumerable<INinjectModule> getNinjectModules()
        {
            return new INinjectModule[]
                   {
                       new InfrastructureModule(), 
                       new ConfigurationModule(), 
                       new PersistenceModule(), 
                       new EventsModule(), 
                   };
        }
    }
}